import BasicTool from '../BasicTool'; 

/**
 * 绘制工具
 */
export default class DrawPolygon {
    /**
     * 构造函数
     * @param viewer
     */
    constructor(viewer) {
        this.viewer = viewer;
        this._drawHandler = null;//事件
        this._dataSource = null;//存储entities
        this._tempPositions = [];//存储点集合
        this._mousePos = null;//移动点
        this._drawType = null;//类型 Point Poliline Polygon Rectangle Circle
        this.basicTool = new BasicTool(viewer)
    }
 
    /**
     * 激活点线面
     * @param drawType
     */
    activate(drawType, callback) {
        this.clearAll();
        this.callback = callback;
        /**
         * 回调结果
         * type：类型       Point-点 Polyline-线 Polygon-面
         * state： 状态     drawing-绘制中  finish-绘制完成
         * points：经纬度  这个是用于保存绘制点时单独返回点           格式是[113.03,23.03,100]
         * points：经纬度集合           格式是[[113.03,23.03,100]]
         * positions：cesium 的点对象集合    格式是cesium的Cartesian对象 绘制类型是点的话，这里就是单独对象，不是数组
         */
        this.callbackResult= {
            type: "",
            state: "",
            point: null,
            points: [],
            positions: []
        };
        this._drawType = drawType;
        this._dataSource = new Cesium.CustomDataSource('polygon_dataSource');
        this.viewer.dataSources.add(this._dataSource);
        this._registerEvents(); //注册鼠标事件
    }
 
    /**
     * 注册鼠标事件
     */
    _registerEvents() {
        this._drawHandler = new Cesium.ScreenSpaceEventHandler(this.viewer.scene.canvas);
        this.viewer.scene.globe.depthTestAgainstTerrain = true;//开启深度测试
        this._leftClickEventForPolygon();
        this._mouseMoveEventForPolygon();
        this._rightClickEventForPolygon();
    }
 
    /**
     * 鼠标事件之绘制面的左击事件
     * @private
     */
    _leftClickEventForPolygon() {
        this._drawHandler.setInputAction((e) => {
            let p = this.viewer.scene.pickPosition(e.position);
            if (!p) return;
            this._tempPositions.push(p);
            this._addPolygon();
        }, Cesium.ScreenSpaceEventType.LEFT_CLICK)
    }
 
    /**
     * 鼠标事件之绘制面的移动事件
     * @private
     */
    _mouseMoveEventForPolygon() {
        this._drawHandler.setInputAction((e) => {
            let p = this.viewer.scene.pickPosition(e.endPosition);
            if (!p) return;
            this._mousePos = p;
        }, Cesium.ScreenSpaceEventType.MOUSE_MOVE)
    }
 
    /**
     * 鼠标事件之绘制面的右击事件
     * @private
     */
    _rightClickEventForPolygon() {
        this._drawHandler.setInputAction((e) => {
            let p = this.viewer.scene.pickPosition(e.position);
            if (!p) return;
            this._tempPositions.push((this._tempPositions)[0])
            console.log("绘制结束", this._tempPositions)
            // 如果没有3个点，无法形成面，直接结束本次操作
            if(Array.from(this._tempPositions).length < 3) {
                this._removeAllEvent();
                this._dataSource.entities.removeAll();
                // 回调
                this.callbackResult = {
                    type: "Polygon",
                    state: "finish",
                    points: [],
                    postions: [],
                }
                this.callback && this.callback(this.callbackResult)
                return;
            }
            this._removeAllEvent();
            this._dataSource.entities.removeAll();
            this._dataSource.entities.add({
                polyline: {
                    positions: this._tempPositions,
                    clampToGround: true,//贴地
                    width: 3,
                    material: new Cesium.PolylineDashMaterialProperty({
                        color: Cesium.Color.YELLOW,
                    }),
                    depthFailMaterial: new Cesium.PolylineDashMaterialProperty({
                        color: Cesium.Color.YELLOW,
                    })
                },
                polygon: {
                    hierarchy: this._tempPositions,
                    extrudedHeightReference: Cesium.HeightReference.CLAMP_TO_GROUND,
                    material: Cesium.Color.YELLOW.withAlpha(0.4),
                    clampToGround: true,
                },
            })
            // 转换为经纬度坐标
            var points = this._tempPositions.map(r=>this.basicTool.cartesian2ArrayLonLat(r))
            // 回调
            this.callbackResult = {
                type: "Polygon",
                state: "finish",
                points: points,
                postions: this._tempPositions,
            }
            this.callback && this.callback(this.callbackResult)
 
        }, Cesium.ScreenSpaceEventType.RIGHT_CLICK)
    }
 
    /**
     * 移除所有鼠标事件
     * @private
     */
    _removeAllEvent() {
        this._drawHandler && (
            this._drawHandler.removeInputAction(Cesium.ScreenSpaceEventType.LEFT_CLICK),
            this._drawHandler.removeInputAction(Cesium.ScreenSpaceEventType.MOUSE_MOVE),
            this._drawHandler.removeInputAction(Cesium.ScreenSpaceEventType.RIGHT_CLICK),
            this._drawHandler.destroy(),
            this._drawHandler = null
        )
        this.drawPoint && this.drawPoint.clearAll()
        this.drawPolyline && this.drawPolyline.clearAll()
        this.drawRectangleTool && this.drawRectangleTool.clearAll()
    }
 
    /**
     * 重置所有参数
     * @private
     */
    _resetParams() {
        if (this._dataSource != null) {
            this._dataSource.entities.removeAll();
            this.viewer.dataSources.remove(this._dataSource);
        }
        this._dataSource = null;
        this._tempPositions = [];
        this._mousePos = null;
        this._drawType = null;
    }
 
    /**
     * 清除
     */
    clearAll() {
        this._removeAllEvent();
        this._resetParams();
    }
 
    /**
     * 画面
     * @private
     */
    _addPolygon() {
        if (this._tempPositions.length == 1) {
            //一个顶点+移动点
            this._dataSource.entities.add({
                polyline: {
                    positions: new Cesium.CallbackProperty(() => {
                        let c = Array.from((this._tempPositions));
                        if (this._mousePos) {
                            c.push(this._mousePos);
                        }
                        // 转换为经纬度坐标
                        var points = c.map(r=>this.basicTool.cartesian2ArrayLonLat(r))
                        // 回调
                        this.callbackResult = {
                            type: "Polygon",
                            state: "drawing",
                            points: points,
                            postions: c,
                        }
                        this.callback && this.callback(this.callbackResult)
                        return c;
                    }, false),
                    clampToGround: true,//贴地
                    width: 3,
                    material: new Cesium.PolylineDashMaterialProperty({
                        color: Cesium.Color.YELLOW,
                    }),
                    depthFailMaterial: new Cesium.PolylineDashMaterialProperty({
                        color: Cesium.Color.YELLOW,
                    })
                }
            })
        } else {
            this._dataSource.entities.removeAll();
            console.log("两个点及以上绘制")
            //两个顶点+移动点
            this._dataSource.entities.add({
                polygon: {
                    hierarchy: new Cesium.CallbackProperty(() => {
                        let poss = Array.from(this._tempPositions);
                        if (this._mousePos) {
                            poss.push(this._mousePos);
                        }
                        // 转换为经纬度坐标
                        var points = poss.map(r=>this.basicTool.cartesian2ArrayLonLat(r))
                        // 回调
                        this.callbackResult = {
                            type: "Polygon",
                            state: "drawing",
                            points: points,
                            postions: poss,
                        }
                        this.callback && this.callback(this.callbackResult)
                        return new Cesium.PolygonHierarchy(poss);
                    }, false),
                    extrudedHeightReference: Cesium.HeightReference.CLAMP_TO_GROUND,
                    material: Cesium.Color.RED.withAlpha(0.4),
                    clampToGround: true,
                },
                polyline: {
                    positions: new Cesium.CallbackProperty(() => {
                        let c = Array.from((this._tempPositions));
                        if (this._mousePos) {
                            c.push(this._mousePos);
                            c.push(c[0]);//与第一个点相连
                        }
                        return c;
                    }, false),
                    clampToGround: true,//贴地
                    width: 3,
                    material: new Cesium.PolylineDashMaterialProperty({
                        color: Cesium.Color.YELLOW,
                    }),
                    depthFailMaterial: new Cesium.PolylineDashMaterialProperty({
                        color: Cesium.Color.YELLOW,
                    })
                }
            })
        }
 
    }
}
